package com.itheima.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.itheima.dto.OrderInfoDto;
import com.itheima.mapper.OrderMapper;
import com.itheima.pojo.Member;
import com.itheima.pojo.Order;
import com.itheima.pojo.OrderSetting;
import com.itheima.service.MemberService;
import com.itheima.service.OrderService;
import com.itheima.service.OrderSettingService;
import com.itheima.utils.DateUtil;
import com.itheima.utils.RedisUtil;
import com.itheima.utils.SnowflakeIdWorker;
import com.itheima.vo.OrderSuccessInfoVO;
import org.apache.dubbo.config.annotation.Service;

import javax.annotation.Resource;
import java.util.*;

@Service
public class OrderServiceImpl extends ServiceImpl<OrderMapper, Order> implements OrderService {

    @Resource
    private MemberService memberService;

    @Resource
    private OrderSettingService orderSettingService;

    @Override
    public Long createOrder(OrderInfoDto orderInfoDto) {
        try {
            Thread.sleep(30000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        //1.短信验证码校验
        String code = RedisUtil.get("sms:code:" + orderInfoDto.getTelephone());//之前给手机号发送的验证码
        String validCode = orderInfoDto.getValidateCode();
        if(code == null){
            throw new RuntimeException("没有发送短信验证码或者短信验证码已过期，请重新发送！");
        }
        if(code.equals(validCode) == false){
            throw new RuntimeException("验证码输入错误！");
        }
        String orderDate = DateUtil.formatDate(orderInfoDto.getOrderDate());
        //2.判断是否重复预约
        //2.1.根据手机号查找会员
        //2.2.会员该日期已经有预约了该套餐
        Member member = memberService.findByTelephone(orderInfoDto.getTelephone());
        if(member != null){
            Order order = this.exists(member.getId(),orderDate);
            if(order != null){
                throw new RuntimeException("您已经预约了，请勿重复预约！");
            }
        }
        //3.当前日期是否可以预约
        OrderSetting orderSetting = orderSettingService.findByDate(orderDate);
        if(orderSetting == null || orderSetting.getNumber() <= 0){
            throw new RuntimeException("今日不可预约");
        }
        if(orderSetting.getNumber().intValue() == orderSetting.getReservations().intValue()){
            throw new RuntimeException("今日预约已满");
        }
        return doCreateOrder(orderInfoDto,orderSetting,member);
    }

    @Override
    public Order exists(Long memberId, String orderDate) {
        QueryWrapper<Order> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("member_id",memberId);
        queryWrapper.eq("order_date",orderDate);
        return this.getOne(queryWrapper);
    }

    @Override
    public OrderSuccessInfoVO selectOrderSuccessInfo(Long orderId) {
        return this.baseMapper.selectOrderSuccessInfo(orderId);
    }

    @Override
    public Map selectSetmealPercent() {
        Map map = new HashMap();
        List<Map> data = this.baseMapper.selectSetmealPercent();
        map.put("seriesData",data);
        List<String> legendData = new ArrayList<>();
        for (Map _map : data){
            legendData.add((String) _map.get("name"));
        }
        map.put("legendData",legendData);
        return map;
    }

    private Long doCreateOrder(OrderInfoDto orderInfoDto,OrderSetting orderSetting,Member member){
        //4.预约设置预约数修改
        orderSetting.setReservations(orderSetting.getReservations() + 1);
        orderSettingService.updateById(orderSetting);
        //5.会员信息维护
        if(member == null){
            member = new Member();
            member.setCreateDate(new Date());
        }
        member.setTelephone(orderInfoDto.getTelephone());
        member.setName(orderInfoDto.getName());
        member.setSex(orderInfoDto.getSex());
        member.setIdCard(orderInfoDto.getIdCard());
        memberService.saveOrUpdate(member);
        //6.预约订单
        Order order = new Order();
        //雪花算法生成唯一ID(20位长度的long类型数据)
        order.setOrderNo(String.valueOf(SnowflakeIdWorker.getInstance().nextId()));
        order.setSetmealId(orderInfoDto.getSetmealId());
        order.setMemberId(member.getId());
        order.setOrderDate(orderInfoDto.getOrderDate());
        order.setPayStatus(0);
        this.save(order);
        return order.getId();
    }

}